package com.gdut.multiusercommunicationsystem.controller;

import com.fasterxml.jackson.databind.ObjectMapper;
import com.gdut.multiusercommunicationsystem.component.OnlineUserManager;
import com.gdut.multiusercommunicationsystem.mapper.*;
import com.gdut.multiusercommunicationsystem.model.*;
import jakarta.annotation.Resource;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import org.springframework.web.socket.CloseStatus;
import org.springframework.web.socket.TextMessage;
import org.springframework.web.socket.WebSocketSession;
import org.springframework.web.socket.handler.TextWebSocketHandler;

import java.io.IOException;
import java.util.List;

@Component
public class WebSocketController extends TextWebSocketHandler {
    @Autowired
    private OnlineUserManager onlineUserManager;
    @Autowired
    private ObjectMapper objectMapper;
    @Resource
    private MessageSessionMapper messageSessionMapper;
    @Autowired
    private MessageMapper messageMapper;

    @Override
    public void afterConnectionEstablished(WebSocketSession session) throws Exception {
        System.out.println("[WebSocket] 连接成功");
        User user = (User) session.getAttributes().get("user");
        if(user==null){
            return ;
        }
        //连接成功就上线
        onlineUserManager.online(user.getUserId(),session);
    }

    @Override
    protected void handleTextMessage(WebSocketSession session, TextMessage message) throws Exception {
        System.out.println("[WebSocket] 收到消息： "+message.toString());
        User user = (User) session.getAttributes().get("user");
        if(user==null){
            return ;
        }
        //将载荷中的信息从jSON转化成MessageRequest类
        MessageRequest messageRequest=objectMapper.readValue(message.getPayload(),MessageRequest.class);
        if(messageRequest.getType().equals("message")){
            transferMessage(user,messageRequest);
        }else{
            System.out.println("[handleTextMessage] 类型有误");
        }
    }

    private void transferMessage(User user, MessageRequest messageRequest) throws IOException {
        //构造一个响应对象
        MessageResponse messageResponse=new MessageResponse();
        messageResponse.setContent(messageRequest.getContent());
        messageResponse.setSessionId(messageRequest.getSessionId());
        messageResponse.setFromId(user.getUserId());
        messageResponse.setFromName(user.getUsername());
        //将响应对象转换成JSON
        String respJson = objectMapper.writeValueAsString(messageResponse);
        //根据sessionId，从数据库中获得这个会话中的userId
        List<Friend> friends=messageSessionMapper.getFriendsBySessionId(messageRequest.getSessionId(),user.getUserId());
        //将自己也加入到friends上，因为要给发送方也发送一条信息
        Friend mySelf=new Friend();
        mySelf.setFriendId(user.getUserId());
        mySelf.setFriendName(user.getUsername());
        friends.add(mySelf);
        //根据刚刚获得的userId，给每个用户都发送一份消息
        for(Friend friend:friends){
            //WebSocketSession是用来发送信息的
            WebSocketSession webSocketSession=onlineUserManager.getSession(friend.getFriendId());
            if(webSocketSession==null){
                continue;
            }
            webSocketSession.sendMessage(new TextMessage(respJson));
        }
        //将这个数据存入数据库，进行持久化
        Message message=new Message();
        message.setFromId(user.getUserId());
        //message.setFromName(user.getUsername());
        message.setSessionId(messageRequest.getSessionId());
        message.setContent(messageRequest.getContent());
        messageMapper.add(message);
    }

    @Override
    public void handleTransportError(WebSocketSession session, Throwable exception) throws Exception {
        System.out.println("[WebSocket] 抛出异常");
        User user = (User) session.getAttributes().get("user");
        if(user==null){
            return ;
        }
        onlineUserManager.offline(user.getUserId(),session);
    }

    @Override
    public void afterConnectionClosed(WebSocketSession session, CloseStatus status) throws Exception {
        System.out.println("[WebSocket] 连接关闭");
        User user = (User) session.getAttributes().get("user");
        if(user==null){
            return ;
        }
        onlineUserManager.offline(user.getUserId(),session);
    }
}